﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Text;
using System.Windows.Forms;

namespace SafeFile
{
    public partial class Md5Form : Form
    {
        public Md5Form()
        {
            InitializeComponent();
        }

        internal void SetFile(string inputFile, string outputFile)
        {
            lbInputFile.Text = inputFile;
            lbOutputFile.Text = outputFile;
        }

        private void Md5Form_Shown(object sender, EventArgs e)
        {
            if (!string.IsNullOrEmpty(lbInputFile.Text))
            {
                workerInput.RunWorkerAsync();
            }
            if (!string.IsNullOrEmpty(lbOutputFile.Text))
            {
                workerOutput.RunWorkerAsync();
            }
        }

        private void Md5Form_FormClosing(object sender, FormClosingEventArgs e)
        {
            if (workerInput.IsBusy)
            {
                workerInput.CancelAsync();
            }
            if (workerOutput.IsBusy)
            {
                workerOutput.CancelAsync();
            }
            Hide();
        }

        private void workerInput_DoWork(object sender, DoWorkEventArgs e)
        {
            ComputeMD5(lbInputFile.Text, workerInput, tbInput);
        }

        private void workerInput_ProgressChanged(object sender, ProgressChangedEventArgs e)
        {
            pbInput.Value = e.ProgressPercentage;
            Application.DoEvents();
        }

        private void workerOutput_DoWork(object sender, DoWorkEventArgs e)
        {
            ComputeMD5(lbOutputFile.Text, workerOutput, tbOutput);
        }

        private void workerOutput_ProgressChanged(object sender, ProgressChangedEventArgs e)
        {
            pbOutput.Value = e.ProgressPercentage;
            Application.DoEvents();
        }

        private void ComputeMD5(string filename, BackgroundWorker worker, TextBox textBox)
        {
            using (var stream = new FileStream(filename, FileMode.Open))
            {
                var length = stream.Length / 100.0;
                var percent = 0;
                var offset = 1.0;
                var md5 = Utils.GetMD5(stream, read =>
                {
                    offset += read;
                    var next = (int)Math.Round(offset / length);
                    if (next == percent)
                    {
                        return;
                    }
                    percent = next;
                    worker.ReportProgress(percent);
                });
                var md5Str = BitConverter.ToString(md5).Replace("-", "");
                textBox.Invoke(new MethodInvoker(() =>
                {
                    textBox.Text = md5Str;
                }));
            }
        }
    }
}
